package com.smartmail.receiving.pop3;

import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.Executors;
import java.util.concurrent.ScheduledFuture;
import java.util.concurrent.TimeUnit;

import android.content.Context;

import com.smartmail.SmartMailPreferences;
import com.smartmail.accounts.MailAccount;
import com.smartmail.receiving.AbstractRetrievalThread;
import com.smartmail.receiving.IncomingMailDBManager;


/**
 * POP3RetrievalThread object is object connecting with POP3 mailbox.
 * Each object of this class has ScheduledExecutorService (getScheduler method)
 * object to which you can send a request to perform tasks on POP3 Mailbox.
 * 
 * These tasks can be stopped and resumed by appropriate methods ( stopThread, resumeThread)
 * 
 * @author Tomek
 *
 */
public class POP3RetrievalThread extends AbstractRetrievalThread {

	/**
	 * Public constructor. 
	 * 
	 * @param account - MailAccount object which identities mailbox which will be handled by this thread
	 * @param manager - incoming mails database manager
	 * @param context - application context
	 */
	public POP3RetrievalThread(MailAccount account,IncomingMailDBManager manager,Context context){
		
		super(account,manager,context);
	
		/**
		 * new single thread executor service - single thread for pop3 complementary purpopses
		 */
		_executor = Executors.newScheduledThreadPool(1);
		
		_onDemandCheckMailboxFutures = new ArrayList<ScheduledFuture>();
		_onDemandDownloadingMsgFututes = new ArrayList<ScheduledFuture>();

	}
	
	@Override
	public boolean resumeThread() {
		
		if( _executor.isShutdown())
			return false;
		
		if(_cycleCheckMailBoxTaskFuture != null)
			_cycleCheckMailBoxTaskFuture.cancel(true);
		
		for(ScheduledFuture onDemandMailboxCheck : _onDemandCheckMailboxFutures){
			
			onDemandMailboxCheck.cancel(true);
		}
		_onDemandCheckMailboxFutures.clear();
		
		for(ScheduledFuture onDemandDownloadMsgs : _onDemandDownloadingMsgFututes){
			
			onDemandDownloadMsgs.cancel(true);
		}
		_onDemandDownloadingMsgFututes.clear();

		// retrieve delay time from Smart Mail Preferences
		int _delayTime = SmartMailPreferences.getInt(SmartMailPreferences.PREFERENCE_INCOMING_MAIL_SERVER_QUERYING_FREQUENCY);
		_cycleCheckMailBoxTaskFuture =
				_executor.scheduleWithFixedDelay(new POP3MailBoxCheckTask(_mailAccount,_context), 1, _delayTime, TimeUnit.SECONDS);
		return true;
	}
	

	@Override
	public boolean stopThread() {
		
		if( _executor.isShutdown() )
			return false;
		
		for(ScheduledFuture onDemandMailboxCheck : _onDemandCheckMailboxFutures){
			
			onDemandMailboxCheck.cancel(true);
		}
		_onDemandCheckMailboxFutures.clear();
		
		for(ScheduledFuture onDemandDownloadMsgs : _onDemandDownloadingMsgFututes){
			
			onDemandDownloadMsgs.cancel(true);
		}
		_onDemandDownloadingMsgFututes.clear();
		
		if(_cycleCheckMailBoxTaskFuture != null)
			_cycleCheckMailBoxTaskFuture.cancel(true);
		
		// mark that checking task is canceled
		_cycleCheckMailBoxTaskFuture = null;
		
		return true;
		
	}

	@Override
	public boolean isRunning() {

		if( _cycleCheckMailBoxTaskFuture == null)
			return false;
		
		return ( !_cycleCheckMailBoxTaskFuture.isCancelled() );
	}

	@Override
	public boolean restartThread() {
		
		if(stopThread())
			if(resumeThread())
					return true;
		return false;
	}

	@Override
	public boolean killThread() {

		_executor.shutdownNow();
		return true;
		
	}
	
	
	/**
	 * logTag for logging purposes
	 */
	private static String _logTag = "com.smartmail.receiving.pop3";
	
	/**
	 * Scheduled Future of check mailbox task
	 */
	private ScheduledFuture _cycleCheckMailBoxTaskFuture = null;
	
	/**
	 * List of on demand mailbox checkings.
	 */
	private List<ScheduledFuture> _onDemandCheckMailboxFutures;
	
	/**
	 * List of messages downloading tasks.
	 */
	private List<ScheduledFuture> _onDemandDownloadingMsgFututes;

	@Override
	public void checkMailbox() {
		
		ScheduledFuture checkMailboxOnDemandTask = 
				_executor.schedule(new POP3MailBoxCheckTask(_mailAccount, _context), 0, TimeUnit.SECONDS);
		_onDemandCheckMailboxFutures.add(checkMailboxOnDemandTask);
		
	}

	@Override
	public void downloadMessages() {
		
		ScheduledFuture downloadMsgsOnDemandTask =
				_executor.schedule(new POP3DownloadMsgsTask(_mailAccount, _context), 0, TimeUnit.SECONDS);
		_onDemandDownloadingMsgFututes.add(downloadMsgsOnDemandTask);
		
	}
}
